/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package ca.trader.sale;

import ca.trader.beans.enterprise.SaleBeanLocal;
import ca.trader.beans.enterprise.UserBeanLocal;
import ca.trader.except.InvalidHttpRequestException;
import ca.trader.except.SaleAlreadyFavouritedByUserException;
import ca.trader.except.SaleDoesNotExistException;
import ca.trader.except.UserNotAuthenticatedException;
import ca.trader.logger.TraderLogger;
import ca.trader.user.User;
import ca.trader.utils.DebugUtils;
import ca.trader.utils.HttpConsts;
import ca.trader.utils.URLUtils;
import java.io.IOException;
import java.io.PrintWriter;
import javax.ejb.EJB;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import org.json.JSONException;
import org.json.JSONObject;

/**
 *
 * @author Ahsan
 */
@WebServlet(name = "FavouriteSaleForAuthenticatedUser", urlPatterns =
{
	 "/FavouriteSaleForAuthenticatedUser"
})
public class FavouriteSaleForAuthenticatedUser extends HttpServlet
{

	 private static final String _className = FavouriteSaleForAuthenticatedUser.class.getName();
	 private static final String PARAM_SALE_ID = "saleID";
	 /**
	  * Reference to the UserBean EJB
	  */
	 @EJB
	 UserBeanLocal userBean;
	 /**
	  * Reference to the SaleBean EJB
	  */
	 @EJB
	 SaleBeanLocal saleBean;
	 private static final String ACTION_SALE_FAVOURITED = "favourited";
	 private static final String ACTION_SALE_UNFAVOURITED = "unfavourited";

	 /**
	  * Processes requests for both HTTP
	  * <code>GET</code> and
	  * <code>POST</code> methods.
	  *
	  * @param request servlet request
	  * @param response servlet response
	  * @throws ServletException if a servlet-specific error occurs
	  * @throws IOException if an I/O error occurs
	  */
	 protected void processRequest(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException
	 {

		  String _methodName = "processRequest";

		  TraderLogger.logInfo(_className, _methodName, "Starting servlent: " + this.getServletName());

		  response.setContentType("text/html;charset=UTF-8");
		  PrintWriter out = response.getWriter();

		  // Get the session object. 
		  HttpSession session = request.getSession();

		  // this variable marks if the operation was successful or not
		  boolean wasSuccess = false;

		  // this varbiable marks whether a failure was unexplained (e.g. database not existing)
		  boolean wasUnexplainedFailure = false;

		  // Contains the reason for the failure if it happens (explained or unexplained)
		  String failureOrSuccessMessage = "";

		  // Incase the failure is unexplained, this will contain the stack trace of the failure
		  String unexplainedFailureReasonStackTrace = "";

		  String actionPerformed = "";;

		  JSONObject jsonObject = new JSONObject(); // for output

		  try
		  {
			   if (request.getParameter(PARAM_SALE_ID) == null)
			   {
				    throw new InvalidHttpRequestException("Invalid Request");
			   }

			   Integer saleID;

			   saleID = Integer.parseInt(request.getParameter(PARAM_SALE_ID));
			   User authenticatedUser = userBean.getAuthenticatedUser(session);

			   TraderLogger.logInfo(_className, _methodName, String.format("Favourting sale.  Sale ID = %d, User ID = %d", saleID, authenticatedUser.getId()));

			   Sale sale = saleBean.getSaleByID(saleID);

			   try
			   {
				    saleBean.favouriteSaleForUser(authenticatedUser, sale);
				    TraderLogger.logInfo(_className, _methodName, "Successfully favourited sale");
				    failureOrSuccessMessage = "Successfully favourited sale.";
				    actionPerformed = ACTION_SALE_FAVOURITED;
			   }
			   catch (SaleAlreadyFavouritedByUserException ex)
			   {
				    TraderLogger.logInfo(_className, _methodName, "Sale is already favourited by user.  Attempting to unfavourite the sale.");

				    saleBean.unfavouriteSaleForUser(authenticatedUser, sale);
				    TraderLogger.logInfo(_className, _methodName, "Successfully unfavourited sale");
				    failureOrSuccessMessage = "Successfully unfavourited sale.";
				    actionPerformed = ACTION_SALE_UNFAVOURITED;

			   }

			   wasSuccess = true;
		  }
		  catch (SaleDoesNotExistException ex)
		  {
			   failureOrSuccessMessage = "No sale found with the specified ID";
		  }
		  catch (NumberFormatException nfe)
		  {
			   failureOrSuccessMessage = "sale ID is not an integer.";
		  }
		  catch (InvalidHttpRequestException ex)
		  {
			   failureOrSuccessMessage = "Invalid request.  Please request from " + URLUtils.getMainWebpage(request) + "/" + HttpConsts.VIEW_SALE_JSP_PAGE;
		  }
		  catch (UserNotAuthenticatedException ex)
		  {
			   failureOrSuccessMessage = "No user is authenticated.  Please authenticate yourself";
		  }
		  /**
		   * Unexplained failure
		   */
		  catch (Exception e)
		  {
			   wasSuccess = false;
			   failureOrSuccessMessage = "Unknown error: " + e.getMessage();

			   wasUnexplainedFailure = true;
			   unexplainedFailureReasonStackTrace = DebugUtils.getStackTraceAsString(e);

		  }
		  finally
		  {
			   /**
			    * If the failure was unexplained, log it
			    */
			   if (wasUnexplainedFailure)
			   {
				    TraderLogger.logSevere(_className, _methodName, failureOrSuccessMessage, unexplainedFailureReasonStackTrace);
			   }

			   try
			   {
				    // add the success attribute to the jsonObject
				    jsonObject.put("success", wasSuccess);
				    jsonObject.put("message", failureOrSuccessMessage);

				    if (!wasSuccess)
				    {
						TraderLogger.logInfo(_className, _methodName, "Unable to favourite sale: " + failureOrSuccessMessage);
				    }
				    else
				    {

						jsonObject.put("action", actionPerformed);
				    }

				    // print the jsonObject
				    out.print(jsonObject.toString());
			   }
			   catch (JSONException ex)
			   {
			   }

			   out.close();


			   TraderLogger.logInfo(_className, _methodName, "Exiting servlent: " + this.getServletName());
		  }
	 }

	 // <editor-fold defaultstate="collapsed" desc="HttpServlet methods. Click on the + sign on the left to edit the code.">
	 /**
	  * Handles the HTTP
	  * <code>GET</code> method.
	  *
	  * @param request servlet request
	  * @param response servlet response
	  * @throws ServletException if a servlet-specific error occurs
	  * @throws IOException if an I/O error occurs
	  */
	 @Override
	 protected void doGet(HttpServletRequest request, HttpServletResponse response)
		    throws ServletException, IOException
	 {
		  processRequest(request, response);
	 }

	 /**
	  * Handles the HTTP
	  * <code>POST</code> method.
	  *
	  * @param request servlet request
	  * @param response servlet response
	  * @throws ServletException if a servlet-specific error occurs
	  * @throws IOException if an I/O error occurs
	  */
	 @Override
	 protected void doPost(HttpServletRequest request, HttpServletResponse response)
		    throws ServletException, IOException
	 {
		  processRequest(request, response);
	 }

	 /**
	  * Returns a short description of the servlet.
	  *
	  * @return a String containing servlet description
	  */
	 @Override
	 public String getServletInfo()
	 {
		  return "Short description";
	 }// </editor-fold>

}
